const { exec } = require('child_process');
const { promisify } = require('util');

const execAsync = promisify(exec);

class KeyboardController {
  constructor() {
    this.lastKeyTime = 0;
    this.minKeyInterval = 100; // 最小按键间隔（毫秒）
  }

  // 发送按键
  async sendKey(key) {
    const startTime = Date.now();

    // 防止按键过快
    const timeSinceLastKey = startTime - this.lastKeyTime;
    if (timeSinceLastKey < this.minKeyInterval) {
      console.log(`按键间隔过短，跳过 (${timeSinceLastKey}ms)`);
      return false;
    }

    try {
      let keyCode;
      
      switch (key) {
        case 'left':
          keyCode = '{LEFT}';
          break;
        case 'right':
          keyCode = '{RIGHT}';
          break;
        default:
          console.error(`未知的按键: ${key}`);
          return false;
      }

      // 使用PowerShell发送按键
      const psScript = `
        Add-Type -AssemblyName System.Windows.Forms
        [System.Windows.Forms.SendKeys]::SendWait("${keyCode}")
      `;

      await execAsync(`powershell -Command "${psScript}"`, {
        timeout: 1000
      });

      this.lastKeyTime = Date.now();
      const executionTime = this.lastKeyTime - startTime;

      console.log(`按键已发送: ${key} (执行时间: ${executionTime}ms)`);

      if (executionTime > 50) {
        console.warn(`警告: 按键执行时间超过50ms (${executionTime}ms)`);
      }

      return true;

    } catch (error) {
      console.error(`发送按键失败 (${key}):`, error.message);
      return false;
    }
  }

  // 尝试激活PowerPoint窗口
  async focusPowerPoint() {
    try {
      const psScript = `
        Add-Type -AssemblyName System.Windows.Forms
        $pptProcess = Get-Process -Name POWERPNT -ErrorAction SilentlyContinue | Where-Object {$_.MainWindowTitle -ne ""} | Select-Object -First 1
        if ($pptProcess) {
          $sig = '[DllImport("user32.dll")] public static extern bool SetForegroundWindow(IntPtr hWnd);'
          $type = Add-Type -MemberDefinition $sig -Name WindowAPI -PassThru
          $result = $type::SetForegroundWindow($pptProcess.MainWindowHandle)
          Write-Output "PowerPoint窗口已激活: $result"
        } else {
          Write-Output "未找到PowerPoint窗口"
        }
      `;

      const { stdout } = await execAsync(`powershell -Command "${psScript}"`, {
        timeout: 2000
      });

      console.log(stdout.trim());
      return stdout.includes('已激活');

    } catch (error) {
      console.error('激活PowerPoint窗口失败:', error.message);
      return false;
    }
  }

  // 检查PowerPoint是否运行
  async isPowerPointRunning() {
    try {
      const { stdout } = await execAsync(
        'powershell -Command "Get-Process -Name POWERPNT -ErrorAction SilentlyContinue | Select-Object -First 1"',
        { timeout: 2000 }
      );

      return stdout.trim().length > 0;

    } catch (error) {
      console.error('检查PowerPoint状态失败:', error.message);
      return false;
    }
  }

  // 发送按键并确保PowerPoint在前台
  async sendKeyWithFocus(key) {
    console.log(`开始处理按键: ${key}`);
    
    // 第1步：尝试激活PowerPoint窗口
    try {
      console.log('尝试激活PowerPoint窗口...');
      const focused = await this.focusPowerPoint();
      if (focused) {
        console.log('PowerPoint窗口激活成功');
        // 等待窗口激活完成
        await new Promise(resolve => setTimeout(resolve, 300));
      } else {
        console.log('PowerPoint窗口激活失败，继续发送按键');
      }
    } catch (error) {
      console.log('激活PowerPoint窗口时出错，继续发送按键:', error.message);
    }

    // 第2步：发送按键
    console.log(`准备发送按键: ${key}`);
    const result = await this.sendKey(key);
    
    if (result) {
      console.log(`按键 ${key} 发送成功`);
    } else {
      console.log(`按键 ${key} 发送失败`);
    }
    
    return result;
  }

  // 增强的按键发送方法
  async sendKeyEnhanced(key) {
    console.log(`增强按键发送: ${key}`);
    
    try {
      let keyCode;
      switch (key) {
        case 'left':
          keyCode = '{LEFT}';
          break;
        case 'right':
          keyCode = '{RIGHT}';
          break;
        default:
          console.error(`未知的按键: ${key}`);
          return false;
      }

      // 使用更强的PowerShell脚本
      const psScript = `
        Add-Type -AssemblyName System.Windows.Forms
        Add-Type -AssemblyName System.Drawing
        
        # 尝试激活PowerPoint窗口
        $pptProcess = Get-Process -Name POWERPNT -ErrorAction SilentlyContinue | Where-Object {$_.MainWindowTitle -ne ""} | Select-Object -First 1
        if ($pptProcess) {
          $sig = '[DllImport("user32.dll")] public static extern bool SetForegroundWindow(IntPtr hWnd);'
          $type = Add-Type -MemberDefinition $sig -Name WindowAPI -PassThru
          $null = $type::SetForegroundWindow($pptProcess.MainWindowHandle)
          Start-Sleep -Milliseconds 200
        }
        
        # 发送按键
        [System.Windows.Forms.SendKeys]::SendWait("${keyCode}")
        Write-Output "按键已发送: ${keyCode}"
      `;

      const startTime = Date.now();
      const { stdout } = await execAsync(`powershell -Command "${psScript}"`, {
        timeout: 3000
      });
      
      const executionTime = Date.now() - startTime;
      console.log(`PowerShell输出: ${stdout.trim()}`);
      console.log(`增强按键执行时间: ${executionTime}ms`);
      
      this.lastKeyTime = Date.now();
      return true;

    } catch (error) {
      console.error(`增强按键发送失败 (${key}):`, error.message);
      return false;
    }
  }
}

module.exports = KeyboardController;
